// 1.  定义一个Promise构造函数，传入`excutor`执行器函数
function Promise(excutor){
    // 2. 在构造函数内定义2个属性
    //    1. `this.PromiseState` 保存promise状态
    //    2. `this.PromiseResult`保存promise结果值
    this.PromiseState = "pending";
    this.PromiseResult = undefined;

    // 新：在对象上添加一个保存（resolve、reject）回调函数的数组 - this.callBacks
    this.callBacks = [];

    // 3. 定义resolve、reject函数
    //    1. 在resolve函数内修改`this.PromiseState` 为`fulfilled`，`this.PromiseResult`为value
    //    2. 在reject函数内修改`this.PromiseState`为 `rejected`,`this.PromiseResult` 为 reason
    let resolve = (value)=>{
        this.PromiseState = 'fulfilled';
        this.PromiseResult = value;
        // 新：判断callBacks是否有长度
        // 如果有 - 遍历数组并执行当中的每一个resolve函数
        if(this.callBacks.length){
           
            this.callBacks.forEach(item=>{
                item.resolve(value);
            })
        }
    }
    let reject = (reason)=>{
        this.PromiseState = 'rejected';
        this.PromiseResult = reason;
        // 新：判断callBacks是否有长度
        // 如果有 - 遍历数组并执行当中的每一个resolve函数
        if(this.callBacks.length){
            this.callBacks.forEach(item=>{
                item.reject(reason);
            })
        }
    }

     // 4. 调用`excutor`函数并传入resolve、reject函数
     // 5. try捕获执行`excutor`函数时抛出错误
        //    1. catch 内调用reject函数并传入err参数
    try{
     excutor(resolve,reject);
    }catch(err){
        reject(err)
    }
}

// 1. 新建promise原型下then方法
Promise.prototype.then = function(onResolve,onReject){

    // 同步操作
    // 2. 判断对象状态为 "fulfilled"，调用onResolve函数，并传入结果值
    if(this.PromiseState === "fulfilled"){
        onResolve(this.PromiseResult);
    }
    // 3. 判断对象状态为 "rejected"，调用onReject函数，并传入结果值
    if(this.PromiseState === 'rejected'){
        onReject(this.PromiseResult)
    }

    //新：添加异步操作 - 当对象状态为"pending"时
    // 先将所有的then方法内的回调存入callBacks数组里-等到后续调用
    if(this.PromiseState === "pending"){ 
        this.callBacks.push({
            resolve:()=>{
                onResolve(this.PromiseResult);
            },
            reject:()=>{
                onReject(this.PromiseResult);
            }
        });
    }
}


